<template>
  <div>
    <label v-if="label"
           :class="{'i-form-item-label-required':isRequired,'label':true}">{{label}}</label>
    <div class="form-item">
      <slot></slot>
      <div v-if="validateState==='error'"
           class="i-form-item-message">{{validateMessage}}</div>
    </div>
  </div>
</template>
<script>
import Emitter from '../../mixins/emitter'
import AsyncValidator from 'async-validator'
export default {
  name: 'i-form-item',
  mixins: [Emitter],
  props: {
    label: {
      type: String,
      default: ''
    },
    prop: {
      type: String
    }
  },
  inject: ['form'],
  data () {
    return {
      isRequired: false,
      validateState: '',
      validateMessage: ''
    }
  },
  computed: {
    // 从form的model中动态得到当前表单组件的数据
    fieldValue () {
      return this.form.model[this.prop]
    }
  },
  methods: {
    // 从form的rules属性中，获取当前formItem的校验规则
    getRules () {
      let formRules = this.form.rules
      formRules = formRules ? formRules[this.prop] : []
      return [].concat(formRules || [])
    },
    // 只支持blur和change，所以过滤出符合要求的rule规则
    getFilteredRule (trigger) {
      const rules = this.getRules()
      return rules.filter(rule => !rule.trigger || rule.trigger.indexOf(trigger) !== -1)
    },
    setRules () {
      let rules = this.getRules()
      if (rules.length) {
        rules.every((rule) => {
          // 如果有必填项，标记出来
          this.isRequired = rule.required
        })
      }
      this.$on('on-form-blur', this.onFieldBlur)
      this.$on('on-form-change', this.onFieldChange)
    },
    // 校验数据
    validate (trigger, callback = function () { }) {
      let rules = this.getFilteredRule(trigger)
      if (!rules || rules.length === 0) {
        return true
      }
      // 设置校验状态
      this.validateState = 'validating'
      // 以下为async-validator调用
      let descriptor = {}
      descriptor[this.prop] = rules
      const validator = new AsyncValidator(descriptor)
      let model = {}
      model[this.prop] = this.fieldValue
      validator.validate(model, { firstFields: true }, errors => {
        this.validateState = !errors ? 'success' : 'error'
        this.validateMessage = errors ? errors[0].message : ''
        callback(this.validateMessage)
      })
    },
    // 重置数据
    resetField () {
      this.validateState = ''
      this.validateMessage = ''
      this.form.model[this.prop] = this.initialValue
    },
    onFieldBlur () {
      this.validate('blur')
    },
    onFieldChange () {
      this.validate('change')
    }
  },
  // 组件渲染的时候，把组件实例缓存在form中
  mounted () {
    if (this.prop) {
      this.dispatch('i-form', 'on-form-item-add', this)
      // 设置初始值，以便在重置时恢复默认值
      this.initialValue = this.fieldValue
      this.setRules()
    }
  },
  // 组件销毁前，将实例从form的缓存中移除
  beforeDestroy () {
    this.dispatch('i-form', 'on-form-item-remove', this)
  }
}
</script>
<style scoped>
.label {
  display: inline-block;
  width: 80px;
}
.form-item {
  display: inline-block;
  margin-left: 5px;
}
.i-form-item-label-required:before {
  content: "*";
  color: red;
}
.i-form-item-message {
  color: red;
}
</style>